<?php
/**
 * Miffos framework
 * ----------------------------------------------
 *
 * Copyright (c) 2008, 2009 Martin Sadový (http://sodae.cz)
 *
 * This source file is subject to the "Miffos license" that is bundled
 * with this package in the file license.txt.
 *
 * @copyright  Copyright (c) 2008, 2009 Martin Sadový
 * @license    license.txt
 * @link       http://miffos.sodae.cz
 * @package    miffos
 * @version    $Id$
 */

class Router extends  ArrayObject{

    private $params = array("namespace"=>"",
                            "controller"=>"",
                            "action"=>"index",
                            "argument"=>array());

    public $routed = false;

    private $query = false;

    /**
     * Get Url
     * @return string
     */
    public function getUrl()
    {
      return Application::get()->Http->getRequestUrl();
    }



    /**
     * Add Route
     * @param string $url
     * @param array $default
     * @return bool
     */
    public function connect($url, $default = array())
    {
        if($this->routed) return false;

        $newPreg = '';
        $nowUrl  = trim($this->getUrl(),"/");
        $url     = trim($url,"/");
        $delete = array();

        if($this->query){
            $pUrl = explode('?',$nowUrl);
        }else{
            $pUrl = array();
            $pUrl[0] = $nowUrl;
        }

        $split = preg_split('#\<\:(\w+)(\[([^>]+)\])?\>#', $url);
        if (count($split) > 1) {
            preg_match_all('#\<\:(\w+)(\[([^>]+)?\])?\>#', $url, $match);

            foreach ($match[3] as $key => $value)
            {
                    $value = (empty($value))?'[^/\?]+':$value;
                    $once = preg_quote($split[$key], '#').'('.trim($value).')';

                    $newPreg .= (array_key_exists($match[1][$key], $default) ? '('.$once.')?' : $once);
                    if(array_key_exists($match[1][$key], $default))
                        $delete[] = $key+$key;
            }
            $newPreg .= $split[$key+1];
        }else{
            $newPreg = $url;
        }

        if(preg_match('#^'.$newPreg.'$#', $pUrl[0], $param)){

            array_shift($param);

            $this->setParameters($default);

            $combination = array();

            if(count($match[1]) > 0){

                foreach($delete as $keyDelete) {
                    if(array_key_exists($keyDelete, $param)) {
                        unset($param[$keyDelete]);
                    }
                }

                $paramOnce = array();
                foreach($param as $aParam){
                    $paramOnce[] = $aParam;
                }
                $param = $paramOnce;

                foreach($match[1] as $paramKey => $paramName){
                    $combination[ $paramName ] = (is_null($param[$paramKey]) AND $default[$paramName])? $default[$paramName] : $param[$paramKey];
                }
                $this->setParameters($combination);
            }

            $this->routed = true;
            return true;
        }

        return false;
    }



    /**
     * set query url type -> parse only Path
     * @param bool $bool
     */
    public function setQueryType($bool)
    {
        $this->query = $bool;
    }



    /**
     * Set param
     * @param array $array
     */
    public function setParameters(array $array)
    {
        foreach($array as $name=>$value){
           if(isset($this->params[$name])){
               $this->params[$name] = $value;
           }else{
               $this->params['argument'][$name] = $value;
           }

        }
    }



    /**
     * Return route param
     * @param string $name
     * @return string
     */
    public function __get($name)
    {
        if(isset($this->params[$name]))
           return $this->params[$name];
        return $this->params['argument'][$name];
    }



    /**
     * ArrayIterator
     * @return  ArrayIterator
     */
    public function getIterator()
    {
        return new ArrayIterator($this);
    }
}


?>